/*
 * Copyright 2013 Agustina Martinez-Garcia

   Licensed under the Apache License, Version 2.0 (the "License");
   you may not use this file except in compliance with the License.
   You may obtain a copy of the License at

       http://www.apache.org/licenses/LICENSE-2.0

   Unless required by applicable law or agreed to in writing, software
   distributed under the License is distributed on an "AS IS" BASIS,
   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   See the License for the specific language governing permissions and
   limitations under the License.
 */
package uk.ljmu.metadata.utilities;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
 * TODO CLEAN METADATAUSTILITIES - FEDORANAMESPACE DUPLICATED CODE
 * @author agustinamartinez
 *
 */
public class MetadataUtilities {
	//MAPS
	/** */
	public final static Map<String, String> NSMAP = new HashMap<String, String>();
	
	static {
		NSMAP.put("foxml", "info:fedora/fedora-system:def/foxml#");
		NSMAP.put("foxml1.1", "info:fedora/fedora-system:FOXML-1.1");
		NSMAP.put("foxml1.0", "info:fedora/fedora-system:FOXML-1.0");
		NSMAP.put("mets", "info:fedora/fedora-system:METSFedoraExt-1.1");
		NSMAP.put("atom", "info:fedora/fedora-system:ATOM-1.0");
	}
	
	public final static Map<String, String> DCMI_ELEMENTS = new HashMap<String, String>();
	
	static {
		DCMI_ELEMENTS.put("collection", "http://purl.org/dc/dcmitype/Collection");
		DCMI_ELEMENTS.put("dataset", "http://purl.org/dc/dcmitype/Dataset");
		DCMI_ELEMENTS.put("event", "	http://purl.org/dc/dcmitype/Event");
		DCMI_ELEMENTS.put("image", "http://purl.org/dc/dcmitype/Image");
		DCMI_ELEMENTS.put("interactiveResource", "http://purl.org/dc/dcmitype/InteractiveResource");
		DCMI_ELEMENTS.put("movingimage", "http://purl.org/dc/dcmitype/MovingImage");
		DCMI_ELEMENTS.put("physicalobject", "	http://purl.org/dc/dcmitype/PhysicalObject");
		DCMI_ELEMENTS.put("service", "	http://purl.org/dc/dcmitype/Service");
		DCMI_ELEMENTS.put("software", "http://purl.org/dc/dcmitype/Software");
		DCMI_ELEMENTS.put("sound", "	http://purl.org/dc/dcmitype/Sound");
		DCMI_ELEMENTS.put("stillimage", "http://purl.org/dc/dcmitype/StillImage");
		DCMI_ELEMENTS.put("text", "	http://purl.org/dc/dcmitype/Text");
	}
	/**
	 * 
	 * Used when adding RDF properties to RDF documents, to distinguish whether
	 * to add an attribute rdf:resource or set the text value of the property
	 *
	 */
	public static enum propertyTypes {
		Class, Resource
	}
	/** Foxml 1.1 Schema name */
	public  static String SCHEMA = "foxml1-1.xsd";
	/** URI for Fedora Model */
	public final static String MODELURI = "info:fedora/fedora-system:def/model#";
	/**
	 * URI for Fedora Content Model
	 */
	public final static String CONTENTMODELURI = "info:fedora/fedora-system:ContentModel-3.0";
	/** URI for Fedora RELS-EXT format */
	public final static String FORMATURI = "info:fedora/fedora-system:FedoraRELSExt-1.0";
	/** RDF Namespace URI */
	public final static String RDFNS = "http://www.w3.org/1999/02/22-rdf-syntax-ns#";
	/** Default Fedora Object Owner name */	
	public final static String OWNER = "fedoraAdmin";
	/** Default root namespace for object identifiers **/
	public final static String OBJECTID = "info:fedora/";
	/** FEDORA MODEL Namespace prefix for RELS-EXT files **/
	public final static String FEDORA_MODEL_NS_PREFIX = "fedora-model";
	/** FEDORA EXTERNAL RELATIONS Namespace prefix for RELS-EXT files **/
	public final static String FEDORA_RELATIONS_NS_PREFIX = "rel";
	/** Fedora Relaionship's namespaces map */
	public final static Map<String, String> RELS_MAP = new HashMap<String, String>();
	
	/**
	 * Prefixes and namespaces used within a RDF RELS-EXT datastream
	 */
	static {
		RELS_MAP.put("rdf", "http://www.w3.org/1999/02/22-rdf-syntax-ns#");		
		RELS_MAP.put("rel", "info:fedora/fedora-system:def/relations-external#");
		//AMG (15/11) JUST USED to obtain dynamically the model
		RELS_MAP.put("rel-ext", "http://www.fedora-commons.org/definitions/1/0/fedora-relsext-ontology.rdfs");
		RELS_MAP.put("rdfs", "http://www.nsdl.org/ontologies/relationships#");
		RELS_MAP.put("oai_dc", "http://www.openarchives.org/OAI/2.0/oai_dc/");
		RELS_MAP.put("dc", "http://purl.org/dc/elements/1.1/");
		RELS_MAP.put("fedora-model", "info:fedora/fedora-system:def/model#");
		RELS_MAP.put("dcterms", "http://purl.org/dc/terms/");
		RELS_MAP.put("ddi2", "http://example.org/ddi2/");
		RELS_MAP.put("qudex", "http://example.org/qudex/");
		RELS_MAP.put("skos", "http://www.w3.org/2004/02/skos/core/");
	}
	
	/** MIMETYPES for Fedora objects map */
	public final static Map<String, String> MIMETYPES_MAP = new HashMap<String, String>();
	
	/**
	 * Constants for expressing all the possible MIMETYPES formats
	 * within fedora objects
	 */
	static {
		MIMETYPES_MAP.put("xml", "text/xml");
		MIMETYPES_MAP.put("plain", "text/plain");
		MIMETYPES_MAP.put("html", "text/html");
		MIMETYPES_MAP.put("html-xml", "text/html+xml");
		MIMETYPES_MAP.put("svg", "text/svg+xml");
		MIMETYPES_MAP.put("rtf", "text/rtf");
		MIMETYPES_MAP.put("jpeg", "image/jpeg");
		MIMETYPES_MAP.put("jp2", "image/jp2");
		MIMETYPES_MAP.put("gif", "image/gif");
		MIMETYPES_MAP.put("bmp", "image/bmp");
		MIMETYPES_MAP.put("png", "image/png");
		MIMETYPES_MAP.put("tiff", "image/tiff");
		MIMETYPES_MAP.put("a-mpeg", "audio/mpeg");
		MIMETYPES_MAP.put("aiff", "audio/x-aiff");
		MIMETYPES_MAP.put("wav", "audio/x-wav");
		MIMETYPES_MAP.put("v-mpeg", "video/mpeg");
		MIMETYPES_MAP.put("quicktime", "video/quicktime");
		MIMETYPES_MAP.put("postscript", "application/postscript");
		MIMETYPES_MAP.put("pef", "application/pdf");
		MIMETYPES_MAP.put("rdf", "application/rdf+xml");
		MIMETYPES_MAP.put("xml", "application/xml");
		MIMETYPES_MAP.put("xml2", "text/xml");
		MIMETYPES_MAP.put("word", "application/vnd.ms-word");
		MIMETYPES_MAP.put("ppt", "application/vnd.ms-powerpoint");
		MIMETYPES_MAP.put("smil", "application/smil");
		MIMETYPES_MAP.put("octet-stream", "application/octet-stream");
		MIMETYPES_MAP.put("tar", "application/x-tar");
		MIMETYPES_MAP.put("zip", "application/zip");
		MIMETYPES_MAP.put("zip2", "application/x-zip");
		MIMETYPES_MAP.put("zip3", "application/x-compress");
		MIMETYPES_MAP.put("zip4", "application/x-compressed");
		MIMETYPES_MAP.put("zip5", "application/x-zip-compressed");
		MIMETYPES_MAP.put("gtar", "application/x-gtar");
		MIMETYPES_MAP.put("gzip", "application/x-gzip");
		MIMETYPES_MAP.put("app-xml", "application/xml");
		MIMETYPES_MAP.put("xhtml-xml", "application/xhtml+xml");
		MIMETYPES_MAP.put("xslt", "application/xslt+xml");
		MIMETYPES_MAP.put("dtd", "application/xml-dtd");
		MIMETYPES_MAP.put("excel", "application/vnd.ms-excel");
		MIMETYPES_MAP.put("excel2", "application/ms-excel");
		MIMETYPES_MAP.put("excel3", "application/x-msexcel");
		MIMETYPES_MAP.put("excel4", "application/x-excel");
		MIMETYPES_MAP.put("excel5", "application/x-dos_ms_excel");
		MIMETYPES_MAP.put("excel6", "application/xls");
		MIMETYPES_MAP.put("excel7", "application/x-xls");
		MIMETYPES_MAP.put("csv", "text/csv");
		MIMETYPES_MAP.put("csv2", "text/comma-separated-values");
	}
	/**
	 * 
	 * @author agustinamartinez
	 *
	 */
	public static enum ValueType {
		//Simple types
		Text,
		Number,
		Boolean,
		URL,
		//Schema specific
		DcElement,
		FoafElement,
		GeoElement,
		BiolElement,
		RdfElement,
		RdfsElement,
		DoapElement,
		QudexElement,
		DdiElement,
		//FEDORA Specific
		RELS_EXT,
		X, 
		E,
		M,
		R,
		DSComposite,
		//AMG (15/11) Used to handle Custom namespaces or Exhibit specific fields
		CustomNs,
		DCTERMS,
		SkosElement
	}
	/**
	 * 
	 */
	public static HashMap<String, String> MDSchemasUrl = new HashMap<String, String>(); 
	static
	{
		MDSchemasUrl.put("dc", "http://purl.org/dc/elements/1.1/");
		MDSchemasUrl.put("foaf", "http://xmlns.com/foaf/0.1/");
		MDSchemasUrl.put("doap", "http://usefulinc.com/ns/doap#");
		MDSchemasUrl.put("geo", "http://www.w3.org/2003/01/geo/wgs84_pos#");
		MDSchemasUrl.put("biol", "http://purl.org/NET/biol/ns#");
		MDSchemasUrl.put("rdf", "http://www.w3.org/1999/02/22-rdf-syntax-ns#");
		MDSchemasUrl.put("rel", "info:fedora/fedora-system:def/relations-external#");
		MDSchemasUrl.put("rel-ext", "http://www.fedora-commons.org/definitions/1/0/fedora-relsext-ontology.rdfs");
		MDSchemasUrl.put("skos", "http://www.w3.org/2004/02/skos/core#");
		MDSchemasUrl.put("dcterms", "http://purl.org/dc/terms/");
		MDSchemasUrl.put("vs", "http://www.w3.org/2003/06/sw-vocab-status/ns#");
		MDSchemasUrl.put("rdfs", "http://www.w3.org/2000/01/rdf-schema#");
		MDSchemasUrl.put("dcmitype", "http://purl.org/dc/dcmitype/");
		MDSchemasUrl.put("qudex", "http://example.org/qudex/");
		MDSchemasUrl.put("ddi2", "http://example.org/ddi2/");
		//AMG (15/11) Custom namespaces or Exhibit specific fields
		MDSchemasUrl.put("ex", "http://example.org/custom/");
		MDSchemasUrl.put("dcterms", "http://purl.org/dc/terms/");
		MDSchemasUrl.put("skos", "http://www.w3.org/2004/02/skos/core/");
	}
	/**
	 * 
	 */
	public static HashMap<String, String> MDSchemasUrl2 = new HashMap<String, String>(); 
	static
	{
		MDSchemasUrl2.put("dc", "http://dublincore.org/2003/03/24/dces");
		MDSchemasUrl2.put("foaf", "http://xmlns.com/foaf/0.1/");
		MDSchemasUrl2.put("doap", "http://usefulinc.com/ns/doap#");
		MDSchemasUrl2.put("geo", "http://www.w3.org/2003/01/geo/wgs84_pos#");
		MDSchemasUrl2.put("biol", "http://purl.org/NET/biol/ns#");
		MDSchemasUrl2.put("rdf", "http://www.w3.org/1999/02/22-rdf-syntax-ns#");
		MDSchemasUrl2.put("rel", "info:fedora/fedora-system:def/relations-external#");
		MDSchemasUrl2.put("rel-ext", "http://www.fedora-commons.org/definitions/1/0/fedora-relsext-ontology.rdfs");
		MDSchemasUrl2.put("skos", "http://www.w3.org/2004/02/skos/core#");
		MDSchemasUrl2.put("dcterms", "http://purl.org/dc/terms/");
		MDSchemasUrl2.put("vs", "http://www.w3.org/2003/06/sw-vocab-status/ns#");
		MDSchemasUrl2.put("rdfs", "http://www.w3.org/2000/01/rdf-schema#");
		MDSchemasUrl2.put("dcmitype", "http://purl.org/dc/dcmitype/");
		MDSchemasUrl2.put("qudex", "http://example.org/qudex/");
		MDSchemasUrl2.put("ddi2", "http://example.org/ddi2/");
		//AMG (15/11) Custom namespaces or Exhibit specific fields
		MDSchemasUrl2.put("ex", "http://example.org/custom/");
		MDSchemasUrl2.put("dcterms", "http://purl.org/dc/terms/");
		MDSchemasUrl2.put("skos", "http://www.w3.org/2004/02/skos/core/");
	}
	/**
	 * REL, REL-EXT mean Fedora rels ontology, added both cause sometimes the prefix is either one of them
	 */
	public static List<String> dynamicParsingSchemasList = new ArrayList<String>(Arrays.asList("dc", "foaf", "doap", "geo", "rdf", "rel-ext", "dcterms", "rdfs", "rel"));
	/**
	 * 
	 */
	public static HashMap<String, ValueType> MDSchemas = new HashMap<String, ValueType>(); 
	static
	{
		MDSchemas.put("dc", ValueType.DcElement);
		MDSchemas.put("foaf", ValueType.FoafElement);
		MDSchemas.put("geo", ValueType.GeoElement);
		MDSchemas.put("biol", ValueType.BiolElement);
		MDSchemas.put("rdf", ValueType.RdfElement);
		MDSchemas.put("doap", ValueType.DoapElement);
		MDSchemas.put("rdfs", ValueType.RdfsElement);
		MDSchemas.put("ddi2", ValueType.DdiElement);
		MDSchemas.put("qudex", ValueType.QudexElement);
		//AMG (15/11) Custom namespaces or Exhibit specific fields
		MDSchemas.put("ex", ValueType.CustomNs);
		//AMG (15/11) To look by prefix
		MDSchemas.put("rel", ValueType.RELS_EXT);
		MDSchemas.put("dcterms", ValueType.DCTERMS);
		MDSchemas.put("skos", ValueType.SkosElement);
	}
	public static enum SCHEMAS_PREFIXES {
		dc, foaf, geo, biol, rdf, doap, rdfs, ddi2, qudex, ex, rel, dcterms
	}
	//METHOD SECTION
	public static String getRelsExtEmptyDocument()
	{
		String doctext = "";
		doctext = "<rdf:RDF xmlns:rdf=\""+ RELS_MAP.get("rdf") + "\" xmlns:rdfs=\"" + RELS_MAP.get("rdfs") + "\" " +
		"xmlns:rel=\"" + RELS_MAP.get("rel") + "\" xmlns:oai_dc=\"" + RELS_MAP.get("oai_dc") + "\" xmlns:dc=\"" 
		+ RELS_MAP.get("dc") + "\" xmlns:fedora-model=\"" + RELS_MAP.get("fedora-model") + "\"></rdf:RDF>";   
		return doctext;
	}
}
